import 'dart:math';

import 'package:flutter/material.dart';
import 'package:get/get.dart';
import 'package:xindong/common/xindong_api_path.dart';
import 'package:xindong/common/xindong_all.dart';
import 'package:xindong/common/xindong_methods.dart';
import 'package:xindong/common/xindong_types.dart';
import 'package:xindong/manager/network/xindong_networking.dart';
import 'package:xindong/manager/xindong_tencent_singleton.dart';
import 'package:xindong/manager/xindong_user_controller.dart';
import 'package:xindong/models/chat_message/xindong_custom_gift_message.dart';
import 'package:xindong/models/gift/xindong_gift_class.dart';
import 'package:xindong/models/user/xindong_user.dart';
import 'package:xindong/routes/conversation/model/xindong_liaotian_detail_class.dart';
import 'package:xindong/utils/xindong_text_util.dart';
import 'package:xindong/widgets/floating_screen/xindong_piao_ping_singleton.dart';
import 'package:tencent_cloud_chat_uikit/business_logic/separate_models/tui_chat_separate_view_model.dart';
import 'package:tencent_cloud_chat_uikit/business_logic/view_models/tui_chat_global_model.dart';
import 'package:tencent_cloud_chat_uikit/tencent_cloud_chat_uikit.dart';
import 'package:tencent_cloud_chat_uikit/ui/controller/tim_uikit_chat_controller.dart';
import 'package:tencent_cloud_chat_uikit/ui/utils/message.dart';

class XinDongChatSingleton extends GetxController {
  // ======== 单例
  // 工厂方法构造函数
  factory XinDongChatSingleton() => _getInstance();

  // instance的getter方法，singletonSingleton.instance获取对象
  static XinDongChatSingleton get instance => _getInstance();

  // 静态变量_instance，存储唯一对象
  static XinDongChatSingleton? _instance;

  // 获取对象
  static XinDongChatSingleton _getInstance() {
    _instance ??= XinDongChatSingleton._internal();
    return _instance!;
  }

  // 私有的自定义命名式构造方法，通过它实现一个类;
  // 子类不能继承internal
  // 不是关键字，可定义其他名字
  XinDongChatSingleton._internal() {
    //初始化(设置一些默认的)...
  }

  // 全局使用的
  static final _chatSeparateVM = TUIChatSeparateViewModel();

  // 局部使用
  final chatController = TIMUIKitChatController();

  // 使用这个去呼叫
  XinDongLiaoTianDetailClass? detailClass;
  V2TimConversation? conversation;

  // 定时计数
  int _timerCount = 0;
  int _timerCountLimit = 10;

  // 聊天使用这个
  TUIChatSeparateViewModel get currentChatSeparateVM {
    return conversation == null ? _chatSeparateVM : chatController.model!;
  }

  requestUserList({int type = ChatType.text, required String content, required dynamic userId}) async {
    var parameters = {
      "type": type,
      "userid": XinDongUserController.to.loginId,
      "touserid": userId,
      "content": content,
    };
    final object = await XinDongNetworking.instance.request(
      XinDongApi.chatUserList,
      method: XinDongHttpMethod.post,
      parameters: parameters,
    );
  }

  // Future<XinDongChatUser?> requestChatUser({required dynamic userId}) async {
  //   var parameters = {
  //     "userId": XinDongUserController.to.loginId,
  //     "touserId": userId,
  //   };
  //
  //   final object = await XinDongNetworking.instance.request(
  //     XinDongApi.chatUserInfo,
  //     method: XinDongHttpMethod.post,
  //     parameters: parameters,
  //   );
  //   if (object.code == XinDongServerStatus.success) {
  //     return XinDongChatUser.fromJson(object.data);
  //   }
  //   return null;
  // }

  Future<XinDongLiaoTianDetailClass?> _requestDetail({required dynamic userId}) async {
    var parameters = {"to_user": userId};
    final object = await XinDongNetworking.instance.request(
      XinDongApi.chatUserDetail,
      method: XinDongHttpMethod.post,
      parameters: parameters,
    );
    if (object.code == XinDongServerStatus.success) {
      detailClass = XinDongLiaoTianDetailClass.fromJson(object.data);
      update();
      return detailClass;
    }
    return null;
  }

  Future<bool> requestCommonSend(
      {required int type,
      required dynamic userId,
      String? content,
      int? second,
      String? cover,
      int? giftId,
      int? giftCount}) async {
    var parameters = {
      "type": type,
      "userid": XinDongUserController.to.loginId,
      "touserid": userId,
    };
    // 内容
    parameters.addIf(content != null, 'content', content);
    // 语音时长
    parameters.addIf(second != null, 'second', second);
    // 视频封面
    parameters.addIf(cover != null, 'cover', cover);
    // 礼物
    parameters.addIf(giftId != null, 'id', giftId);
    parameters.addIf(giftCount != null, 'num', giftCount);

    showLoading(maskColor: Colors.transparent, showLoading: false);
    final object = await XinDongNetworking.instance.request(
      XinDongApi.chatSendMessage,
      method: XinDongHttpMethod.post,
      parameters: parameters,
    );
    if (type == ChatType.gift) {
      hideLoading();
      if (object.code == 200) {
        try {
          final result = await XinDongTencentSingleton.instance.sendCustomMessage(
            userId: '',
            groupID: XinDongTencentSingleton.IM_GIFT_ROOM,
            chatSeparateVM: chatController.model!,
            data: object.data,
          );
          if (result) {
            final message = XinDongCustomGiftMessage.fromJson(object.data);
            XinDongPiaoPingSingleton.instance.addQueue(message);
          }
        } catch (e) {
          mCatchPrint(e);
        }
      }
      return object.code == 200 || object.code == 201;
    } else
    // 非礼物code = 0,不是200
    if (object.code == 0) {
      if (chatController.model != null) {
        await XinDongTencentSingleton.instance.sendCustomMessage(
          userId: userId,
          groupID: "",
          chatSeparateVM: chatController.model!,
          data: object.data,
        );
      } else {
        mDebugPrint("chatVM需要赋值，需要在会话页配置chatController");
      }
    }
    hideLoading();
    return object.code == 0;
  }

  Future<bool> requestSendText({XinDongUser? targetUser, required String text}) async {
    targetUser ??= detailClass?.another;
    // convID不带c2c
    final convID = conversation?.userID ?? targetUser?.uid ?? "";
    if (TextUtil.isEmpty(convID)) {
      mDebugPrint("convID无效");
      return false;
    }
    V2TimValueCallback<V2TimMessage>? result = await MessageUtils.handleMessageError(
      currentChatSeparateVM.sendTextMessage(text: text, convID: convID, convType: ConvType.c2c),
      currentContext(),
    );
    if (result != null) {
      Future.delayed(Duration.zero).whenComplete(() {
        XinDongTencentSingleton.instance.errorCode(result, targetUser);
      });
      return result.code == 0;
    }
    return false;
  }

  Future<bool> requestSendImage({XinDongUser? targetUser, required String filePath}) async {
    targetUser ??= detailClass?.another;
    // convID不带c2c
    final convID = conversation?.userID ?? targetUser?.uid ?? "";
    if (TextUtil.isEmpty(convID)) {
      mDebugPrint("convID无效");
      return false;
    }
    V2TimValueCallback<V2TimMessage>? result = await MessageUtils.handleMessageError(
      currentChatSeparateVM.sendImageMessage(imagePath: filePath, convID: convID, convType: ConvType.c2c),
      currentContext(),
    );
    if (result != null) {
      Future.delayed(Duration.zero).whenComplete(() {
        XinDongTencentSingleton.instance.errorCode(result, targetUser);
      });
      return result.code == 0;
    }
    return false;
  }

  Future<bool> requestSendVoice({XinDongUser? targetUser, required String filePath, required int second}) async {
    targetUser ??= detailClass?.another;
    // convID不带c2c
    final convID = conversation?.userID ?? targetUser?.uid ?? "";
    if (TextUtil.isEmpty(convID)) {
      mDebugPrint("convID无效");
      return false;
    }
    V2TimValueCallback<V2TimMessage>? result = await MessageUtils.handleMessageError(
      currentChatSeparateVM.sendSoundMessage(
          soundPath: filePath, duration: second, convID: convID, convType: ConvType.c2c),
      currentContext(),
    );
    if (result != null) {
      Future.delayed(Duration.zero).whenComplete(() {
        XinDongTencentSingleton.instance.errorCode(result, targetUser);
      });
      return result.code == 0;
    }
    return false;
  }

  Future<bool> requestSendVideo({XinDongUser? targetUser, required String filePath, required String coverPath}) async {
    targetUser ??= detailClass?.another;
    // convID不带c2c
    final convID = conversation?.userID ?? targetUser?.uid ?? "";
    if (TextUtil.isEmpty(convID)) {
      mDebugPrint("convID无效");
      return false;
    }
    V2TimValueCallback<V2TimMessage>? result = await MessageUtils.handleMessageError(
      currentChatSeparateVM.sendVideoMessage(
          videoPath: filePath, snapshotPath: coverPath, convID: convID, convType: ConvType.c2c),
      currentContext(),
    );
    if (result != null) {
      Future.delayed(Duration.zero).whenComplete(() {
        XinDongTencentSingleton.instance.errorCode(result, targetUser);
      });
      return result.code == 0;
    }
    return false;
  }

  Future<bool> requestSayHello({XinDongUser? targetUser, required String text}) async {
    targetUser ??= detailClass?.another;
    final data = {"type": ChatType.sayHello, "content": text, "score": 0};
    return XinDongTencentSingleton.instance.sendCustomMessage(
      data: data,
      userId: targetUser?.uid ?? "",
      groupID: "",
      chatSeparateVM: currentChatSeparateVM,
    );
  }

  Future<bool> sayHello({required XinDongUser user,required bool free}) {
    String text = "你好呀！";
    final list = XinDongAll.instance.chatCommonWords;
    if (list.isNotEmpty) {
      int number = Random().nextInt(list.length);
      text = list[number].content;
    }
    if (free) {
      return requestSayHello(text: text, targetUser: user);
    } else {
      return requestSendText(text: text, targetUser: user);
    }
  }

// Future<bool> requestSendText({required dynamic userId, required String text}) async {
//   return requestCommonSend(type: ChatType.sayHello, userId: userId, content: text);
// }
//
// Future<bool> requestSendImage({required dynamic userId, required String filePath}) async {
//   final fileUrl = await XinDongNetworking.instance.uploadFile(filePath: filePath);
//   if (TextUtil.isEmpty(fileUrl)) {
//     return false;
//   }
//   mDebugPrint('返回文件结果$fileUrl');
//   return requestCommonSend(type: ChatType.image, userId: userId, content: fileUrl!);
// }
//
// Future<bool> requestSendVoice({required dynamic userId, required String filePath, required int second}) async {
//   final fileUrl = await XinDongNetworking.instance.uploadFile(filePath: filePath);
//   if (TextUtil.isEmpty(fileUrl)) {
//     return false;
//   }
//   mDebugPrint('返回文件结果$fileUrl');
//   return requestCommonSend(type: ChatType.voice, userId: userId, content: fileUrl!, second: second);
// }
//
// Future<bool> requestSendVideo({required dynamic userId, required String filePath, required String coverPath}) async {
//   final fileUrl = await XinDongNetworking.instance.uploadFiles(filePaths: [filePath, coverPath]);
//   if (TextUtil.isEmpty(fileUrl)) {
//     return false;
//   }
//   mDebugPrint('返回文件结果$fileUrl');
//   List list = fileUrl!.stringToList();
//   return requestCommonSend(type: ChatType.video, userId: userId, content: list.first, cover: list.last);
// }
//
  Future<bool> requestSendGift({required dynamic userId, required XinDongGiftClass model, required int count}) async {
    return requestCommonSend(type: ChatType.gift, userId: userId, giftId: model.id, giftCount: count);
  }
}

extension IntimateExtension on XinDongChatSingleton {
  // 设置当前用户
  Future<XinDongLiaoTianDetailClass?> getDetails(String? userId) async {
    if (userId == null) {
      Get.back();
      return null;
    }
    detailClass = await _requestDetail(userId: userId);
    if (detailClass == null) {
      Get.back();
      return null;
    }
    // 如果ID不一致，则重置
    if (detailClass?.another.uid != userId) {
      _timerCount = 0;
    }
    return detailClass;
  }

  // 计数触发
  void countTrigger(String userId) async {
    // 不能
    if (detailClass == null || detailClass!.another.uid != userId) {
      return;
    }
    try {
      _timerCount++;
      if (_timerCount >= _timerCountLimit) {
        directTrigger();
      }
    } catch (error) {
      mCatchPrint(error);
    }
  }

  // 直接触发，一般用在消耗钻石的时候
  Future<void> directTrigger() async {
    // 不能
    if (detailClass == null) {
      return Future.value();
    }
    _timerCount = 0;
    return _requestProgress();
  }

  // 请求亲密度
  Future<void> _requestProgress() async {
    // 不在聊天页，可以不更新亲密度
    if (detailClass == null) {
      return Future.value();
    }
    detailClass = await _requestDetail(userId: detailClass!.another.uid);
    update();
    return Future.value();
  }

  // 本地修改
  void addIntimacy() {
    // intimacyProgressClass?..nextLevelNeed = intimacyProgressClass!.nextLevelNeed - 4;
    update();
  }
}
